home *** CD-ROM | disk | FTP | other *** search
/ PC World Komputer 2010 April / PCWorld0410.iso / pluginy Firefox / 684 / 684.xpi / chrome / fireftp.jar / content / js / connection / transfer.js < prev   
Text File  |  2009-06-11  |  12KB  |  306 lines

  1. function transfer() {
  2.   this.prompt             = true;
  3.   this.skipAll            = false;
  4.   this.cancel             = false;
  5.   this.busy               = false;
  6.   this.didRefreshLaterSet = false;
  7.   this.remoteRefresh      = '';
  8.   this.localRefresh       = '';
  9. }
  10.  
  11. transfer.prototype = {
  12.   start : function(download, aFile, aLocalParent, aRemoteParent, aListData) {
  13.     if (!gFtp.isConnected || this.cancel || remoteTree.isLoading
  14.       || ( download && !aFile && remoteTree.selection.count == 0 && !aLocalParent)
  15.       || (!download && !aFile && localTree.selection.count  == 0 && !aLocalParent)) {
  16.       return;
  17.     }
  18.  
  19.     if (this.busy) {                                         // we're doing locking, sort of, see below
  20.       var self = this;
  21.       var currentListData = aListData ? aListData : cloneArray(gFtp.listData);
  22.       var func = function() { self.start(download, aFile, aLocalParent, aRemoteParent, currentListData); };
  23.       setTimeout(func, 500);
  24.       return;
  25.     }
  26.  
  27.     var localParent  = aLocalParent  ? aLocalParent  : gLocalPath.value;
  28.     var remoteParent = aRemoteParent ? aRemoteParent : gRemotePath.value;
  29.     var files        = new Array();
  30.     var resume;
  31.     var listData     = aListData ? aListData : gFtp.listData;
  32.  
  33.     if (gNoPromptMode) {                                     // overwrite dialog is disabled, do overwrites
  34.       this.prompt = false;
  35.     }
  36.  
  37.     if (aFile) {                                             // populate the files variable with what we're transfering
  38.       files.push(aFile);
  39.     } else if (download) {                                   // download specific
  40.       if (aRemoteParent) {                                   // if recursive
  41.         files = listData;
  42.       } else {                                               // if not recursive
  43.         for (var x = 0; x < remoteTree.rowCount; ++x) {
  44.           if (remoteTree.selection.isSelected(x)) {
  45.             files.push(remoteTree.data[x]);
  46.           }
  47.         }
  48.       }
  49.     } else {                                                 // upload specific
  50.       if (aLocalParent) {                                    // if recursive
  51.         try {
  52.           var dir     = localFile.init(localParent);
  53.           var innerEx = gFireFTPUtils.getFileList(dir, new wrapperClass(files));
  54.  
  55.           if (innerEx) {
  56.             throw innerEx;
  57.           }
  58.         } catch (ex) {
  59.           debug(ex);
  60.           return;                                            // skip this directory
  61.         }
  62.       } else {                                               // if not recursive
  63.         for (var x = 0; x < localTree.rowCount; ++x) {
  64.           if (localTree.selection.isSelected(x)) {
  65.             if (!localFile.verifyExists(localTree.data[x])) {
  66.               continue;
  67.             }
  68.  
  69.             files.push(localTree.data[x]);
  70.           }
  71.         }
  72.       }
  73.     }
  74.  
  75.     if (download && aLocalParent) {
  76.       localDirTree.addDirtyList(aLocalParent);
  77.     } else if (!download && aRemoteParent) {
  78.       remoteDirTree.addDirtyList(aRemoteParent);
  79.     }
  80.  
  81.     for (var x = 0; x < files.length; ++x) {
  82.       var fileName = files[x].leafName;
  83.  
  84.       if ((download && gDownloadCaseMode == 1) || (!download && gUploadCaseMode == 1)) {
  85.         fileName = fileName.toLowerCase();                   // special request to change filename case
  86.       } else if ((download && gDownloadCaseMode == 2) || (!download && gUploadCaseMode == 2)) {
  87.         fileName = fileName.toUpperCase();                   // special request to change filename case
  88.       }
  89.  
  90.       if (this.getPlatform() == "windows") {                  // scrub out illegal characters on windows / \ : * ? | " < >
  91.         fileName = fileName.replace(/[/\\:*?|"<>]/g, '_');
  92.       }
  93.  
  94.       var remotePath = !download ? gFtp.constructPath     (remoteParent, fileName) : files[x].path;
  95.       var localPath  =  download ? localTree.constructPath(localParent,  fileName) : files[x].path;
  96.       var file;
  97.  
  98.       if (download) {                                        // check to see if file exists
  99.         file           = localFile.init(localPath);
  100.       } else {
  101.         file           = { exists: function() { return false; } };
  102.         var remoteList = aRemoteParent ? listData : remoteTree.data;
  103.  
  104.         for (var y = 0; y < remoteList.length; ++y) {
  105.           if (remoteList[y].leafName == fileName) {
  106.             file       = { fileSize: remoteList[y].fileSize, lastModifiedTime: remoteList[y].lastModifiedTime, leafName: fileName, exists: function() { return true; },
  107.                            isDir: remoteList[y].isDirectory(), isDirectory: function() { return this.isDir }};
  108.             break;
  109.           }
  110.         }
  111.       }
  112.  
  113.       if (files[x].fileSize >= 4294967296) {
  114.         error(gStrbundle.getFormattedString("tooBig", [files[x].leafName]));
  115.         continue;
  116.       }
  117.  
  118.       if (this.skipAll && file.exists() && !file.isDirectory()) {
  119.         continue;
  120.       }
  121.  
  122.       resume = false;
  123.  
  124.       if (file.exists() && this.prompt && !files[x].isDirectory()) {
  125.         resume = file.fileSize < files[x].fileSize && gFtp.detectAscii(remotePath) != 'A';  // ask nicely if file exists
  126.  
  127.         var params = { response         : 0,
  128.                        fileName         : download ? localPath : remotePath,
  129.                        resume           : true,
  130.                        replaceResume    : !resume,
  131.                        existingSize     : file.fileSize,
  132.                        existingDate     : file.lastModifiedTime,
  133.                        newSize          : files[x].fileSize,
  134.                        newDate          : files[x].lastModifiedTime,
  135.                        timerEnable      : !gDisableDestructMode };
  136.  
  137.         this.busy = true;                                    // ooo, the fun of doing semi-multi-threaded stuff in firefox
  138.                                                              // we're doing some 'locking' above
  139.  
  140.         for (var y = 0; y < gMaxCon; ++y) {
  141.           gConnections[y].waitToRefresh = true;
  142.         }
  143.  
  144.         window.openDialog("chrome://fireftp/content/confirmFile.xul", "confirmFile", "chrome,modal,dialog,resizable,centerscreen", params);
  145.  
  146.         for (var y = 0; y < gMaxCon; ++y) {
  147.           gConnections[y].waitToRefresh = false;
  148.         }
  149.  
  150.         this.busy = false;
  151.  
  152.         if (params.response == 1) {
  153.           resume       = false;
  154.         } else if (params.response == 2) {
  155.           this.prompt  = false;
  156.           resume       = false;
  157.         } else if ((params.response == 3) || (params.response == 0)) {
  158.           continue;
  159.         } else if (resume && params.response == 4) {
  160.           resume       = true;
  161.         } else if (!resume && params.response == 4) {
  162.           this.cancel  = true;
  163.  
  164.           for (var y = 0; y < gMaxCon; ++y) {
  165.             if (gConnections[y].isConnected) {
  166.               gConnections[y].abort();
  167.             }
  168.           }
  169.           break;
  170.         } else if (params.response == 5) {
  171.           this.skipAll = true;
  172.           continue;
  173.         }
  174.       }
  175.  
  176.       if (!this.didRefreshLaterSet) {
  177.         this.didRefreshLaterSet = true;
  178.  
  179.         if ((download && !aLocalParent) || this.localRefresh) {
  180.           gFtp.localRefreshLater  = this.localRefresh  ? this.localRefresh  : localParent;
  181.         }
  182.  
  183.         if ((!download && !aRemoteParent) || this.remoteRefresh) {
  184.           gFtp.remoteRefreshLater = this.remoteRefresh ? this.remoteRefresh : remoteParent;
  185.         }
  186.       }
  187.  
  188.       if (download) {
  189.         if (files[x].isDirectory()) {                        // if the directory doesn't exist we create it
  190.           if (!file.exists()) {
  191.             try {
  192.               file.create(Components.interfaces.nsILocalFile.DIRECTORY_TYPE, 0755);
  193.             } catch (ex) {
  194.               debug(ex);
  195.               error(gStrbundle.getFormattedString("failedDir", [remotePath]));
  196.               continue;
  197.             }
  198.           }
  199.  
  200.           this.downloadHelper(localPath, remotePath);
  201.         } else {                                             // download the file
  202.           var connection = this.getConnection();
  203.           connection.download(remotePath, localPath, files[x].fileSize, resume, resume ? file.fileSize : -1, files[x].isSymlink());
  204.         }
  205.       } else {
  206.         if (files[x].isDirectory()) {                        // if the directory doesn't exist we create it
  207.           if (!file.exists()) {
  208.             gFtp.makeDirectory(remotePath);
  209.             gFtp.listData = new Array();                     // we know the new directory is empty
  210.             this.start(false, '', localPath, remotePath);
  211.           } else {
  212.             this.uploadHelper(localPath, remotePath);
  213.           }
  214.         } else {
  215.           var connection = this.getConnection();
  216.           connection.upload(localPath, remotePath, resume, files[x].fileSize, resume ? file.fileSize : -1);
  217.         }
  218.       }
  219.     }
  220.   },
  221.  
  222.   downloadHelper : function(localPath, remotePath) {
  223.     var self = this;
  224.     var func = function() {                                  // we use downloadHelper b/c if we leave it inline the closures will apply
  225.       self.start(true,  '', localPath, remotePath);
  226.     };
  227.     gFtp.list(remotePath, func, true);
  228.   },
  229.  
  230.   uploadHelper   : function(localPath, remotePath) {
  231.     var self = this;
  232.     var func = function() {                                  // we use uploadHelper   b/c if we leave it inline the closures will apply
  233.       gFtp.removeCacheEntry(remotePath);
  234.       self.start(false, '', localPath, remotePath);
  235.     };
  236.     gFtp.list(remotePath, func, true);
  237.   },
  238.  
  239.   getConnection : function(func) {
  240.     if (gConcurrent == 1) {                                                 // short circuit
  241.       return gFtp;
  242.     }
  243.  
  244.     for (var x = 0; x < gConcurrent && x < gMaxCon; ++x) {
  245.       if (gConnections[x].isConnected && gConnections[x].isReady) {         // pick the first ready connection
  246.         return gConnections[x];
  247.       }
  248.  
  249.       if (x && !gConnections[x].isConnected && gConnections[x].type != 'bad' && !gConnections[x].isReady && !gConnections[x].eventQueue.length) {
  250.         gConnections[x].featMLSD   = gFtp.featMLSD;                         // copy over feats b/c we add to the queue even b/f connecting
  251.         gConnections[x].featMDTM   = gFtp.featMDTM;
  252.         gConnections[x].featXMD5   = gFtp.featXMD5;
  253.         gConnections[x].featXSHA1  = gFtp.featXSHA1;
  254.         gConnections[x].featXCheck = gFtp.featXCheck;
  255.         gConnections[x].featModeZ  = gFtp.featModeZ;
  256.  
  257.         gConnections[x].connect();                                          // turn on a connection
  258.         return gConnections[x];
  259.       }
  260.     }
  261.  
  262.     var minConnection = gFtp;
  263.     var minSize       = Number.MAX_VALUE;
  264.  
  265.     for (var x = 0; x < gConcurrent && x < gMaxCon; ++x) {                  // if all connections are busy add to the queue with the least bytes to be transferred
  266.       if (gConnections[x].type == 'bad') {
  267.         continue;
  268.       }
  269.  
  270.       var size = 0;
  271.  
  272.       for (var y = 0; y < gConnections[x].eventQueue.length; ++y) {
  273.         if (gConnections[x].eventQueue[y].cmd == "PASV" && parseInt(gConnections[x].eventQueue[y].callback2)) {
  274.           size += gConnections[x].eventQueue[y].callback2;
  275.         }
  276.       }
  277.  
  278.       if (gConnections[x].dataSocket) {
  279.         size += gConnections[x].dataSocket.progressEventSink.bytesTotal;
  280.         size += gConnections[x].dataSocket.dataListener.bytesTotal;
  281.       }
  282.  
  283.       if (size < minSize) {
  284.         minConnection = gConnections[x];
  285.         minSize       = size;
  286.       }
  287.     }
  288.  
  289.     return minConnection;
  290.   },
  291.  
  292.   getPlatform : function() {
  293.     var platform = navigator.platform.toLowerCase();
  294.  
  295.     if (platform.indexOf('linux') != -1) {
  296.       return 'linux';
  297.     }
  298.  
  299.     if (platform.indexOf('mac') != -1) {
  300.       return 'mac';
  301.     }
  302.  
  303.     return 'windows';
  304.   }
  305. };
  306.